package sceneGraph;

import java.io.*;
import java.util.*;
import javax.vecmath.*;

public class ObjectMesh implements ISceneObject {

	private int numTriangles = 0;
	List<ObjectTriangle> triangles;
	Map<Point3f, Vector3f> db;

	@Override
	public void accept(Visitor visitor) {
		visitor.visit(this);
	}

	public ObjectMesh(String filename, float scaleFactor) {
		triangles = new ArrayList<ObjectTriangle>();
		db = new HashMap<Point3f, Vector3f>();

		int numPoints = 0;
		try {
			InputStreamReader confFile = new InputStreamReader(getClass().getResourceAsStream(filename));
			BufferedReader bufRead = new BufferedReader(confFile);

			// Read file header
			String firstLine = bufRead.readLine();
			if (firstLine.equals("OFF")) {
				String[] args = bufRead.readLine().split(" ");
				if (args.length < 2) {
					throw new IOException("Bad file format");
				}

				numPoints = Integer.parseInt(args[0]);
				numTriangles = Integer.parseInt(args[1]);
			} else {
				numPoints = Integer.parseInt(firstLine);
				numTriangles = Integer.parseInt(bufRead.readLine());
			}

			// Read all points
			String[] curParams;
			List<Point3f> points = new ArrayList<Point3f>();
			Point3f p1, p2, p3;
			for (int i = 0; i < numPoints; i++) {
				curParams = bufRead.readLine().split(" ");
				Point3f curPoint = new Point3f(stringArrToFloatArr(curParams));
				curPoint.scale(scaleFactor);
				points.add(curPoint);
				db.put(curPoint, new Vector3f(0, 0, 0));
			}

			// Read all triangles
			for (int i = 0; i < numTriangles; i++) {
				curParams = bufRead.readLine().split(" ");
				p1 = points.get(Integer.parseInt(curParams[1]));
				p2 = points.get(Integer.parseInt(curParams[2]));
				p3 = points.get(Integer.parseInt(curParams[3]));
				ObjectTriangle curTriangle = new ObjectTriangle(p1, p2, p3);
				triangles.add(curTriangle);
				db.get(p1).add(curTriangle.getNormal1());
				db.get(p2).add(curTriangle.getNormal2());
				db.get(p3).add(curTriangle.getNormal3());
			}

			bufRead.close();
		} catch (Exception e) {
			System.err.println("Error reading configuration file: " + e.getMessage());
		}
	}

	public static float[] stringArrToFloatArr(String[] strArr) {
		float[] db = new float[strArr.length];

		for (int i = 0; i < strArr.length; i++) {
			db[i] = Float.parseFloat(strArr[i]);
		}

		return db;
	}

	public List<ObjectTriangle> getTriangles() {
		return triangles;
	}

}
